package com.mxprojects.gui
{
	import com.mxprojects.io.Utils;
	
	import flash.display.MovieClip;
	import flash.geom.Rectangle;
	import flash.text.TextField;
	
	public class Emoticons extends MovieClip
	{	
		public static const MAX_AMOUNT_PER_MESSAGE:int = 25;
		private static const EMOTES:Array = new Array(":)", ":(", ";)", ":br:", ":?", ":awe:", ":baby:", "8)", ":evil:", ":D", ":heart:", ":kiss:", ":grin:", ":ninja:", ":red:", ":roll:", ":rolleyes:", "8s", ":zzz:", ":P", ":weird:", ":whistle:");
		
		private static var textField:TextField;
		private static var bgColour:uint;
		private static var SPACE_WIDTH:int = 0;
		
		public function Emoticons(){}
		
		public static function parse(textBox:TextField, backgroundColour:uint, CSSStyle:String):void {
			//this will look through the textfield and see if there are any emoticons to parse
			textField = textBox;
			bgColour = backgroundColour;
			
			//if the space width isn't set yet, we should do that
			if(SPACE_WIDTH == 0){
				var oldMessage:String = textField.htmlText;
				textField.htmlText = '<span class="' + CSSStyle + '"><font size="2"> </font></span>';
				SPACE_WIDTH = textField.getCharBoundaries(0).width;
				textField.htmlText = oldMessage;
			}
									
			//prepare the text for emotes first, then put them on
			prepareText();
			placeEmotes();
		}
		
		public static function count(text:String):int {
			//this allows you to count the amount of emoticons in a message. Useful for limiting how many a user puts in
			var emoteCount:int = 0;
			
			for(var i:int = 0; i < EMOTES.length; i++){
				//search the string for the emotes
				var pattern:RegExp = new RegExp(Utils.escapeRegEx(EMOTES[i]), "gi");
				emoteCount += text.match(pattern).length;
			}
			
			return emoteCount;
		}
		
		public static function remove(postItem:PostItem):void {
			//removes all the emoticons from the text field
			var postChildren:int = postItem.numChildren;
			for(var i:int = postChildren - 1; i >= 0; i--){
				if(postItem.getChildAt(i) is Emoticons){
					//smoke it
					postItem.removeChildAt(i);
				}
			}
		}
		
		private static function prepareText():void {
			//check to see if the text has been prepared for the emotes
			for(var i:int = 0; i < EMOTES.length; i++){			
				//check if we've already put emotes there, to do so just find the first instance
				if(textField.text.indexOf(EMOTES[i]) != -1){
					//so we have stuff, let's see if an emote is there
					var checkIndex:int = textField.text.indexOf(EMOTES[i]);
					var checkEmote:Emoticons = textField.parent.getChildByName("emote" + checkIndex) as Emoticons;
										
					if(!checkEmote){						
						//find all instances of the emotes and make them invisible
						var changeColour:String = '<font size="2" color="#' + bgColour.toString(16) + '">' + EMOTES[i] + '</font>';
						
						//find all the emotes case in-sensative
						var colourPattern:RegExp = new RegExp(Utils.escapeRegEx(EMOTES[i]), "gi");
						textField.htmlText = textField.htmlText.replace(colourPattern, changeColour);
						
						//compare the width of the emote text vs. the emote itself
						var emote:Emoticons = new Emoticons();
						emote.gotoAndStop(EMOTES[i]);
												
						//get the first and last chars of the emote to get the width
						var firstChar:Rectangle = textField.getCharBoundaries(checkIndex);
						var lastChar:Rectangle = textField.getCharBoundaries(checkIndex + EMOTES[i].length - 1);
						
						//make sure things went normal
						if(firstChar && lastChar){
							var charWidth:int = (lastChar.x + textField.x) - (firstChar.x + textField.x) + lastChar.width;
							
							//setup var for the replacement
							var emoteText:String = EMOTES[i];
							
							//if our emo width is greater than the char width, then we need to pad the text
							if(emote.width > charWidth){
								var spaceCount:int = Math.floor((emote.width - charWidth) / SPACE_WIDTH);
								emoteText += Utils.buildBlankString(spaceCount);								
							}
											
							//find all the emotes case in-sensative (again)
							var pattern:RegExp = new RegExp(Utils.escapeRegEx(EMOTES[i]), "gi");
							textField.htmlText = textField.htmlText.replace(pattern, emoteText);
							
							//trash the emote now since it's useless
							emote = null;
						}
					}
				}
			}
		}
		
		private static function placeEmotes():void {
			var startIndex:int = 0;
			
			for(var i:int = 0; i < EMOTES.length; i++){
				while((startIndex = textField.text.indexOf(EMOTES[i], startIndex)) != -1) {
					
					//get the first and last chars of the emote to get the width
					var firstChar:Rectangle = textField.getCharBoundaries(startIndex);
					var lastChar:Rectangle = textField.getCharBoundaries(startIndex + EMOTES[i].length - 1);
					
					//make sure the bounds are there. It's rare they aren't, but it's happened
					if(firstChar && lastChar){
						//get the x/y of where the instance was found
						var xPos:int = firstChar.x + textField.x;
						var yPos:int = firstChar.y + textField.y;
						
						var width:int = (lastChar.x + textField.x) - (firstChar.x + textField.x) + lastChar.width;
						
						//see if the emote is already there
						var emote:Emoticons = textField.parent.getChildByName("emote" + startIndex) as Emoticons;
						
						//if it's not go ahead and make it
						if(!emote){
							var newEmote:Emoticons = new Emoticons();
							newEmote.name = "emote" + startIndex;
							newEmote.gotoAndStop(EMOTES[i]);
							emote = newEmote;
							textField.parent.addChild(newEmote);
						}
						
						//put the emote where it needs to go
						emote.x = xPos;
						emote.y = yPos;
					}
					
					//move past the instance and then start searching the rest
					startIndex += EMOTES[i].length;	
				}
			}
		}
	}
}